package com.atguigu.gulimall.member.service.impl;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import com.atguigu.common.utils.HttpUtils;
import com.atguigu.common.vo.MemberLoginVo;
import com.atguigu.gulimall.member.dao.MemberLevelDao;
import com.atguigu.gulimall.member.entity.MemberLevelEntity;
import com.atguigu.gulimall.member.exception.PhoneExsitException;
import com.atguigu.gulimall.member.exception.UserNameExsitException;
import com.atguigu.gulimall.member.service.MemberLevelService;
import com.atguigu.gulimall.member.vo.MemberRegistVo;
import com.atguigu.gulimall.member.vo.SocialUserVo;
import org.apache.http.HttpResponse;
import org.apache.http.util.EntityUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
import org.springframework.stereotype.Service;

import java.util.HashMap;
import java.util.Map;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.atguigu.common.utils.PageUtils;
import com.atguigu.common.utils.Query;

import com.atguigu.gulimall.member.dao.MemberDao;
import com.atguigu.gulimall.member.entity.MemberEntity;
import com.atguigu.gulimall.member.service.MemberService;


@Service("memberService")
public class MemberServiceImpl extends ServiceImpl<MemberDao, MemberEntity> implements MemberService {


    @Autowired
    MemberLevelDao memberLevelDao;

    @Override
    public PageUtils queryPage(Map<String, Object> params) {
        IPage<MemberEntity> page = this.page(
                new Query<MemberEntity>().getPage(params),
                new QueryWrapper<MemberEntity>()
        );

        return new PageUtils(page);
    }

    @Override
    public void regist(MemberRegistVo memberRegistVo) {
        MemberDao memberDao = this.baseMapper;
        MemberEntity memberEntity = new MemberEntity();
        // 1、拿到用户默认会员等级
        MemberLevelEntity memberLevelEntity = memberLevelDao.getDefaultLevel();
        memberEntity.setLevelId(memberLevelEntity.getId());
        // 2、拿到用户名和手机号
        String userName = memberRegistVo.getUserName();
        String phone = memberRegistVo.getPhone();
        // 3、并验证是否唯一,不唯一抛出异常
        checkUserNameUnique(userName);
        checkPhoneUnique(phone);
        // 4、设置相关属性
        memberEntity.setUsername(userName);
        memberEntity.setNickname(memberRegistVo.getUserName());
        memberEntity.setMobile(memberRegistVo.getPhone());
        // 5、密码进行加密，防止数据库密码泄露后被别人登录
        BCryptPasswordEncoder passwordEncoder = new BCryptPasswordEncoder();
        String encode = passwordEncoder.encode(memberRegistVo.getPassword());
        memberEntity.setPassword(encode);
        // 6、保存
        memberDao.insert(memberEntity);
    }


    /**
     * 验证用户名是否唯一
     * @param username
     * @throws UserNameExsitException
     */
    @Override
    public void checkUserNameUnique(String username) throws UserNameExsitException {
        MemberDao memberDao = this.baseMapper;
        Integer count = memberDao.selectCount(new QueryWrapper<MemberEntity>().eq("username", username));
        if (count > 0) {
            // 没有就抛出异常
            throw new UserNameExsitException();
        }
    }

    /**
     * 验证手机号是否唯一
     * @param phone
     * @throws PhoneExsitException
     */
    @Override
    public void checkPhoneUnique(String phone)  throws PhoneExsitException  {
        MemberDao memberDao = this.baseMapper;
        Integer count = memberDao.selectCount(new QueryWrapper<MemberEntity>().eq("mobile", phone));
        if (count > 0) {
            // 没有就抛出异常
            throw new PhoneExsitException();
        }
    }

    @Override
    public MemberEntity login(MemberLoginVo vo) {
        String loginacct = vo.getLoginacct();
        String password = vo.getPassword();

        // 1、根据用户名和手机号查询是否拥有该用户
        MemberDao memberDao = this.baseMapper;
        MemberEntity memberEntity = memberDao.selectOne(new QueryWrapper<MemberEntity>()
                .eq("username", loginacct)
                .or()
                .eq("mobile", loginacct));
        if (memberEntity == null) {
            // 2、没有该用户返回null
            return null;
        } else {
            // 3、拿到用户密码进行解密，验证是否相等
            String passwordDB = memberEntity.getPassword();
            BCryptPasswordEncoder passwordEncoder = new BCryptPasswordEncoder();
            // 4、和用户密码进行校验
            boolean matches = passwordEncoder.matches(password, passwordDB);
            if (matches) {
                // 5、密码验证成功
                return memberEntity;
            } else {
                // 6、密码不相等返回null
                return null;
            }
        }
    }

    @Override
    public MemberEntity OauthLogin(SocialUserVo vo) throws Exception {
        /**
         * 微博社交用户登录有两种情况
         *  1、系统中存在该社交用户，则进行更新该社交用户属性
         *  2、系统中不存在该社交用户，发送请求查询该社交用户信息，并进行注册
         */
        // 1、查看是否用户社交用户唯一id
        MemberDao memberDao = this.baseMapper;
        MemberEntity memberEntity = memberDao.selectOne(new QueryWrapper<MemberEntity>().eq("social_uid", vo.getUid()));

        // 2、社交用户为空
        if (memberEntity != null) {
            // 更新社交用户相关属性
            MemberEntity updateEntity = new MemberEntity();
            updateEntity.setAccessToken(vo.getAccess_token());
            updateEntity.setExpiresIn(vo.getExpires_in());
            // 更新
            this.updateById(updateEntity);
            // 再将access_token放到对象中进行返回
            memberEntity.setAccessToken(vo.getAccess_token());
            memberEntity.setExpiresIn(vo.getExpires_in());
            return memberEntity;
        } else { // 用户为空
            MemberEntity regist = new MemberEntity();
            try {
                // 根据微博开放平台API中 根据access_token和uid发送请求查询用户信息
                //https://api.weibo.com/2/users/show.json
                Map<String,String> map = new HashMap<>();
                map.put("access_token",vo.getAccess_token());
                map.put("uid",vo.getUid());

                HttpResponse response = HttpUtils.doGet("https://api.weibo.com/"
                        , "2/users/show.json"
                        , "get"
                        , new HashMap<>()
                        , map);

                if (response.getStatusLine().getStatusCode() == 200) {
                    // 将请求结果转成json
                    String json = EntityUtils.toString(response.getEntity());
                    // 可以创建Vo进行接收，此处使用 JSONObject 进行接收
                    JSONObject jsonObject = JSON.parseObject(json);
                    String name = jsonObject.getString("name"); // 用户微博姓名
                    String gender = jsonObject.getString("gender"); // 用户微博姓名
                    // 。。。可以拿到多个信息
                    regist.setNickname(name); // 用户昵称
                    regist.setGender("m".equals(gender) ? 1 : 0); // m性别为男,否则性别是女
                }
            } catch (Exception e) {
                e.printStackTrace();
            }
            // 设置社交用户属性后进行保存
            regist.setAccessToken(vo.getAccess_token());
            regist.setSocialUid(vo.getUid());
            regist.setExpiresIn(vo.getExpires_in());
            memberDao.insert(regist);
            return memberEntity;
        }
    }

}